package com.application.TextNode;


import it.unipr.ce.dsg.s2p.sip.Address;

import java.util.ArrayList;

import org.w3c.dom.Document;
import org.w3c.dom.Element;

import ReadWriteXML.CMember;
import ReadWriteXML.ReadXML;
import android.app.AlertDialog;
import android.content.Context;
import android.content.DialogInterface;
import android.graphics.Canvas;
import android.graphics.Color;
import android.os.CountDownTimer;
import android.util.AttributeSet;
import android.util.Log;
import android.view.MotionEvent;
import android.view.SurfaceHolder;
import android.view.SurfaceView;

import com.application.Controller.NetworkController;
import com.application.Controller.ReadWriteFileController;

public class BoardViewTN extends SurfaceView implements SurfaceHolder.Callback{
	public static float horizontal = 100;
	public static float vertical = 50;
	public static int T_MOVE = 1;
	public static int T_NEW = 2;
	public static int T_UPDATE = 3;
	private SurfaceHolder holder;
	public BoardLoopThread loopThread;
	private TextNode tree;
	TextMenu tMenu;
	DetailNode detail=new DetailNode();
	public int control = T_MOVE;
	float xDown = -1, yDown = -1, xUp = -1, yUp = -1, x = -1, y = -1;
	private boolean isNew = false;
	private TextNode cNode = null;
	private TextNode newNode = null;
	long downTime = 0, longTime = 0, upTime = 0, tempTime = 0;
	private boolean isTouchUp = false, isTouchDown = false;
	int id = 1;
	int cId = -1;
	public long idnode = 0;
	private long pID;
	public static boolean isActive=false;
	public BoardViewTN(Context context) {
		super(context);
		init();
	}
	
	public BoardViewTN(Context context, AttributeSet attrs) {
		super(context, attrs);
		init();
	}

	public BoardViewTN(Context context, AttributeSet attrs, int defStyle) {
		super(context, attrs, defStyle);
		init();
	}

	
	private void init() {
		isActive=true;
		getHolder().addCallback(this);
		loopThread = new BoardLoopThread(this);
		tree=new TextNode(id++, "[Tiêu đề]", "[Node gốc]",2,3," ");
		tMenu=new TextMenu();
		this.control = T_MOVE;
	}
	
	@Override
	protected void onDraw(Canvas canvas) {
		canvas.drawColor(Color.rgb(240, 240, 240));
//		canvas.drawColor(Color.rgb(183, 222, 232));
		tree.onDraw(canvas);
		//tMenu.onDraw(canvas);
		detail.onDraw(canvas);
	}
	
	@Override
	public boolean onTouchEvent(MotionEvent event) {
		int action=event.getAction()&MotionEvent.ACTION_MASK;
		switch (action) {
		case MotionEvent.ACTION_DOWN:
			touchDown(event.getX(), event.getY());
			break;
		case MotionEvent.ACTION_MOVE:
			touchMove(event.getX(), event.getY());
			break;
		case MotionEvent.ACTION_UP:
			//touchUp(event.getX(), event.getY());
			break;
		case MotionEvent.ACTION_POINTER_DOWN:
			
			break;
		default:
			break;
		}
		return true;
	}

	private void touchDown(float x, float y) {
		this.isTouchUp = false;
		this.isTouchDown = true;
		downTime = System.currentTimeMillis();
		control = T_MOVE;
		INodeText collistionNode=tree.getCollision(x, y);
		if(collistionNode!=null){
			cNode=(TextNode) collistionNode;
			cId=(int) collistionNode.id;			
		}else{
			cNode=null;
			cId=-1;
		}
		if (downTime - tempTime < 400) {
			if (cNode != null && cId != -1)
				control = T_UPDATE;

		}
		final float _x = x, _y = y;
		CountDownTimer count = new CountDownTimer(1000, 10) {
			boolean moved = false;

			@Override
			public void onTick(long millisUntilFinished) {
				if (BoardViewTN.this.x != _x || BoardViewTN.this.y != _y) {
					moved = true;
				}
			}
			

			@Override
			public void onFinish() {				
				if (!moved && !isTouchUp) {
					if (cNode != null && cId != -1) {
						pID=cNode.getId();
						//An
						ArrayList<INodeText> arrayNode = cNode.getChildren();
//						Log.d("An","so luong arraynode: " + arrayNode.size());
//						Log.d("An","ID parent: " + cNode.getParentId());
//						if(arrayNode.size() != 0){
//							Log.d("An","arrayNode ko Null");
//
//							Long parentid = cNode.getParentId();
//							newNode=new TreeNode(id++, "[Mới thêm]", cNode.getX() + 20, cNode.getY() + 60, "phu");
//							for(INode inode : arrayNode){
//								float y = inode.getY();
//								inode.setY(y + newNode.getY());
//							}
//							tree.autoArrangeTextNode();
//							newNode.setParentId(cNode.getId());
//							cNode.add(newNode);
//							cNode = newNode;
//						}else{
//							Log.d("An","arrayNode Null");
//							newNode=new TreeNode(id++, "[Mới thêm]", _x, _y, "abc");							
//							newNode.setParentId(cNode.getId());
//							cNode.add(newNode);
//							tree.autoArrangeTextNode();
//							cNode = newNode;
						alerDialogWithList();
						control = T_NEW;
//						}
					}
				}
			}
		}.start();
		this.xDown = x;
		this.yDown = y;
		this.x = x;
		this.y = y;		
	}

	private void touchUp(float x, float y) {
		tempTime = downTime;
		Log.d("Phu", "detail "+(System.currentTimeMillis()-downTime));
		if(System.currentTimeMillis()-downTime<200){
			detail=new DetailNode(cNode);	
			//Toast.makeText(getContext(), "detail", 1).show();
		}
		if (control == T_UPDATE) {
//			AlertDialog.Builder alert = new AlertDialog.Builder(this.getContext());
//			final EditText input = new EditText(this.getContext());
//			input.setText(cNode.text);
//			alert.setTitle("Nhập nội dung!");
//			alert.setView(input);
//			alert.setPositiveButton("Cập nhật", new DialogInterface.OnClickListener() {
//				@Override
//				public void onClick(DialogInterface dialog, int which) {
//					cNode.setText(input.getText().toString());
//				}
//			});
//			alert.setNegativeButton("Sắp xếp", new DialogInterface.OnClickListener() {
//
//				@Override
//				public void onClick(DialogInterface dialog, int which) {
////					cNode.autoArrangeTextNode();
//				}
//			});
//			alert.setNeutralButton("Xóa node này", new DialogInterface.OnClickListener() {
//
//				@Override
//				public void onClick(DialogInterface dialog, int which) {
//					Toast.makeText(getContext(), "Xoa node co id=" + cNode.id, 1).show();				
//					tree.remove(cNode);
//					tree.autoArrangeTextNode();	
//				}
//			});
//			alert.show();

		} else if (control == T_NEW) {
//			AlertDialog.Builder alert = new AlertDialog.Builder(this.getContext());
//			final EditText input = new EditText(this.getContext());
//			// input.setText("");
//			alert.setTitle("Nhập nội dung!");
//			alert.setView(input);
//			alert.setPositiveButton("Thêm", new DialogInterface.OnClickListener() {
//				@Override
//				public void onClick(DialogInterface dialog, int which) {
//					newNode.setText(input.getText().toString());	
//					//newNode.setY(cNode.y+cNode.heigh+40);
//				}
//			});
//			alert.setNegativeButton("Hủy bỏ", new DialogInterface.OnClickListener() {
//
//				@Override
//				public void onClick(DialogInterface dialog, int which) {					
//					tree.remove(newNode);
//					tree.autoArrangeTextNode();
//				}
//			});
//			alert.show();
			
		}
		cId = -1;
		this.isTouchUp = true;
		this.isTouchDown = false;
		xUp = x;
		yUp = y;
		this.x = x;
		this.y = y;
		control = -1;
		upTime = System.currentTimeMillis();
	}

	private void touchMove(float x, float y) {
		float moveX, moveY, kcX, kcY;
		if (control == T_NEW && newNode != null)
			newNode.setPostion(x, y);
		else if (control == T_MOVE) {
			moveX = x - this.x;
			moveY = y - this.y;
			if (cId != -1 && cNode != null) {
				
				//cNode.setPostion(cNode.x + moveX, cNode.y + moveY);
//				cNode.moveAll(moveX, moveY);
//				if(detail!=null&&detail.node==cNode){
//					detail.moveAll(moveX,moveY);
//				}

			} else {
				tree.moveAll(moveX, moveY);
				if(detail!=null){
					detail.moveAll(moveX,moveY);
				}
			}
			
		}
		this.x = x;
		this.y = y;
	}

	@Override
	protected void onMeasure(int widthMeasureSpec, int heightMeasureSpec) {
		super.onMeasure(widthMeasureSpec, heightMeasureSpec);
		// this.setMeasuredDimension(widthMeasureSpec, heightMeasureSpec);
	}

//	public boolean addNode(int parentId, TreeNode node) {
//		Log.d("Phu", "Add node in BoardView");
//		{
//			try {
//				if (parentId == -1) {
//					node.setParentNode(null);
//
//				} else {
//					for (TreeNode item : listNode.getData()) {
//
//						if (item.getId() == parentId) {
//							node.setParentNode(item);
//							break;
//						} else
//							node.setParentNode(null);
//					}
//				}
//				node.setBoardView(this);
//				this.listNode.add(node);
//			} catch (Exception e) {
//
//				Log.d("PhuLoi", "Lỗi trong hàm BoardView . addNode" + e.getMessage());
//				return false;
//			}
//			return true;
//		}
//	}

//	public ListNode getNodes() {
//		return this.listNode;
//	}

	public void setTool(int tool) {
		this.control = tool;
	}

//	public void clearNode() {
//		listNode.clear();
//	}

	@Override
	public void surfaceChanged(SurfaceHolder holder, int format, int width, int height) {
		// TODO Auto-generated method stub

	}

	@Override
	public void surfaceCreated(SurfaceHolder holder) {
		Log.d("Phu", "surfaceCreated BoardView ");

		if (loopThread.getState() == Thread.State.TERMINATED) {
			loopThread = new BoardLoopThread(this);
			loopThread.setRunning(true);
			loopThread.start();
		} else {
			loopThread.setRunning(true);
			loopThread.start();
		}
	}

	@Override
	public void surfaceDestroyed(SurfaceHolder holder) {
		isActive=false;
		Log.d("Phu", "surfaceDestroyed BoardView");
		boolean retry = true;
		loopThread.setRunning(false);
		while (retry) {
			try {
				loopThread.join();
				retry = false;
			} catch (InterruptedException e) {

			}
		}
	}

	public void removeNode(TextNode node) {
//		if (node == null || node.id == 0) {
//			Log.d("Phu", "return mat roi " + (node == null ? "null" : node.id);
//			return;
//		}
//		int id = (int) node.id;
//		Log.d("Phu", "cid=:" + id);
//		list.add(node);
//		Log.d("Phu", "size=:" + this.listNode.size());
//		for (int i = 0; i < this.listNode.size(); i++) {
//
//			if (this.listNode.get(i).getParentNode() != null) {
//				Log.d("Phu", "node i=" + i + " co id=" + this.listNode.get(i).getId());
//				if (this.listNode.get(i).getParentNode().getId() == id) {
//					Log.d("Phu", "Tien hanh xoa node id=" + this.listNode.get(i).getId());
//					removeNode(this.listNode.get(i));
//				}
//			}
//		}
		tree.remove(node);
	}

	public void sapXepCay(TextNode node) {
//		int id = node.getId();
//		ArrayList<TreeNode> children = new ArrayList<TreeNode>();
//		for (int i = 0; i < listNode.size(); i++) {
//			if (listNode.get(i).getParentNode() != null && listNode.get(i).getParentNode().getId() == id) {
//				children.add(listNode.get(i));
//			}
//		}
//		float firstX = node.getX() + TreeNode.width;
//		// firstX-=horizontal*children.size();
//		firstX -= TreeNode.width * children.size();
//		if (children.size() > 2)
//			firstX /= 2;
//		float firstY = node.getY() + TreeNode.heigh + vertical;
//		for (int i = 0; i < children.size(); i++) {
//			children.get(i).setX(firstX + i * (TreeNode.width) + TreeNode.width / 2);
//			children.get(i).setY(firstY);
//			sapXepCay(children.get(i));
//		}
	}
	public void writeXML(String path){
//		tree.writeXML(path);
	}
	
	//An
	public void alerDialogWithList(){
		final CharSequence[] items = {"Thêm Mới", "Cập Nhật", "Xóa"};

		AlertDialog.Builder builder = new AlertDialog.Builder(this.getContext());
		builder.setTitle("Thao tác ");
		builder.setItems(items, new DialogInterface.OnClickListener() {
		    public void onClick(DialogInterface dialog, int item) {
		        Log.d("An", "gia tri dialog: " + item + items[item]);
		        if(item == 0)
		        	alerDialogCreateNewNode();
		        else if(item == 1)
		        	alerDialogUpdateNode();
		        else if(item == 2)
		        	alerDialogDelateNode();
		    }
		});
		builder.show();
		//AlertDialog alert = builder.create();
	}

	public void alerDialogCreateNewNode(){
		if(cNode.getId() == 1){
			Log.d("An", "Id: " + cNode.getId());
			final MyDialog dialog=new MyDialog(getContext(),"Tạo node mới!");
			dialog.show();
			Log.d("An", "ok click:"+dialog.isOkClick());
			dialog.setOKClickListener(new MyHandlerInterface() {
				
				@Override
				public void onHandle(Object obj) {
					final float _x = x, _y = y;
					newNode=new TextNode(id++,"[Tiêu đề]", "[Mới thêm]", _x, _y, "abc");							
					cNode.add(newNode);
					tree.autoArrangeTextNode();
					cNode = newNode;
					newNode.setText(dialog.getText());
					newNode.setTitle(dialog.getTextTitle());
					newNode.setMcolor(dialog.getColor());
					Log.d("An", "Idnew: " + newNode.getId());
					
					//Gửi thông tin cho các thành viên
					ArrayList<CMember> members=ReadWriteFileController.readMember(ReadWriteFileController.MEMBER_PATH);
					for(CMember m:members){
						Log.d("An", "pID" + pID +"-"+ m.get_ip());
						NetworkController.sendAddTextNode(new Address(m.get_ip()), pID, newNode);
						
					}
				}
			});
			dialog.setCancelClickListener(new MyHandlerInterface() {
				
				@Override
				public void onHandle(Object obj) {
					dialog.cancel();
				}
			});
		}
		else{
			Log.d("An", "Id..: " + cNode.getId());
			final MyDialog dialog=new MyDialog(getContext(),"Tạo node mới!", cNode.getTitle());
			dialog.show();
			Log.d("An", "ok click:"+dialog.isOkClick());
			dialog.setOKClickListener(new MyHandlerInterface() {
				
				@Override
				public void onHandle(Object obj) {
					final float _x = x, _y = y;
					newNode=new TextNode(id++,"[Tiêu đề]", "[Mới thêm]", _x, _y, "abc");							
					cNode.add(newNode);
					tree.autoArrangeTextNode();
					cNode = newNode;
					newNode.setMcolor(dialog.getColor());
					newNode.setText(dialog.getText());
					newNode.setTitle(dialog.getTextTitle());
					newNode.setMcolor(dialog.getColor());
				}
			});
			dialog.setCancelClickListener(new MyHandlerInterface() {
				
				@Override
				public void onHandle(Object obj) {
					dialog.cancel();
				}
			});
		}
		
	}
	
	public void alerDialogUpdateNode(){
		final MyDialog dialog=new MyDialog(getContext(),"Cập nhật node!",cNode.getTitle(),cNode.getText());
		dialog.show();
		Log.d("An", "ok click:"+dialog.isOkClick());
		dialog.setOKClickListener(new MyHandlerInterface() {
			
			@Override
			public void onHandle(Object obj) {
				cNode.setText(dialog.getText().toString());
				cNode.setTitle(dialog.getTextTitle());
				//newNode.setMcolor(dialog.getColor());
			}
		});
		dialog.setCancelClickListener(new MyHandlerInterface() {
			
			@Override
			public void onHandle(Object obj) {
				dialog.cancel();
			}
		});
	}
	
	public void alerDialogDelateNode(){
		tree.remove(cNode);
		tree.autoArrangeTextNode();
	}
	public void addNode(long idParent, INodeText node){
		Log.d("Phu","BoardView.addNode: pid="+idParent);
		INodeText p=tree.getById(idParent);
		Log.d("Phu","BoardView.addNode " +(p==null));
		if(p!=null){
			Log.d("Phu","da add: pid="+idParent);
			p.add(node);
		}
	}
	public void addNode(long idParent, INodeText node,String path){
		Log.d("Phu","Boardview.addNode:"+path);
		if(!isActive){
			this.readXml(path);
			INodeText p=tree.getById(idParent);
			if(p!=null)
				p.add(node);
			writeXML(path);
		}else{
			addNode(idParent, node);
		}
	
	}
	
	public void readXml(String path){
		Document doc=ReadXML.BuildXML(path);
		tree=new TextNode();
		tree.readXML((Element)doc.getFirstChild().getFirstChild());
	}
	//end
}
